#include "hisurfaceview.h"

#include <android/native_window_jni.h>

#include "util/jni_util.h"
#include "util/log_util.h"

// long nativeCreated(Surface surface);
jlong nativeCreated(JNIEnv *env, jobject thiz, jobject surface) {
  ANativeWindow *window = nullptr;
  if (surface) {
    window = ANativeWindow_fromSurface(env, surface);
  }
  if (!window) {
    LOGW("ANativeWindow is null, ignored");
    return 0;
  }

  auto view = new HiSurfaceView(window);

  return reinterpret_cast<jlong>(view);
}

// void nativeChanged(long nativeRef, Surface surface,
//     int format, int width, int height);
void nativeChanged(JNIEnv *env, jobject thiz, jlong ref, jobject surface,
    jint format, jint width, jint height) {
  if (ref == 0) return;
  auto view = reinterpret_cast<HiSurfaceView *>(ref);
  view->OnWindowChanged(ANativeWindow_fromSurface(env, surface),
      format, width, height);
}

// void nativeDestroyed(long nativeRef);
void nativeDestroyed(JNIEnv *env, jobject thiz, jlong ref) {
  if (ref == 0) return;
  auto view = reinterpret_cast<HiSurfaceView *>(ref);
  delete view;
}

// register natives

CJNIEXPORT jint JNICALL JNI_OnLoad(JavaVM *jvm, void */*reserved*/) {
  JNIEnv *env = nullptr;
  if (jvm->GetEnv(reinterpret_cast<void**>(&env), JNI_VERSION_1_6) != JNI_OK) {
    LOGW("JNI_OnLoad GetEnv error");
    return JNI_ERR;
  }

  static JNINativeMethod methods[] = {
    {"nativeCreated", "(Landroid/view/Surface;)J", reinterpret_cast<void*>(nativeCreated)},
    {"nativeChanged", "(JLandroid/view/Surface;III)V", reinterpret_cast<void*>(nativeChanged)},
    {"nativeDestroyed", "(J)V", reinterpret_cast<void*>(nativeDestroyed)},
  };
  registerNatives(env, "cc/eevee/jni/libsamples/HiSurfaceView", methods,
      sizeof(methods) / sizeof(methods[0]));

  return JNI_VERSION_1_6;
}

CJNIEXPORT void JNICALL JNI_OnUnload(JavaVM */*jvm*/, void */*reserved*/) {
}
